package pe.com.hermes.hermetic.web.controller.consultas;

import java.io.InputStream;

import java.io.OutputStream;


import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;

import java.util.Map;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JasperRunManager;
import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource;

import org.apache.log4j.Logger;

import org.apache.poi.hssf.usermodel.HSSFWorkbook;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.SessionAttributes;


import pe.com.hermes.hermetic.beans.AuditBean;

import pe.com.hermes.hermetic.beans.ConfBean;
import pe.com.hermes.hermetic.beans.EstadoBean;
import pe.com.hermes.hermetic.beans.TiposBean;
import pe.com.hermes.hermetic.negocio.managerimpl.pedido.atm.PedidoAtmContainerManagerImpl;
import pe.com.hermes.hermetic.negocio.managerimpl.pedido.atm.PedidoAtmManagerImpl;
import pe.com.hermes.hermetic.negocio.service.HermeticFacade;
import pe.com.hermes.hermetic.negocio.service.PedidoService;
import pe.com.hermes.hermetic.negocio.service.TablService;
import pe.com.hermes.hermetic.negocio.ultil.ConstantesHermetic;
import pe.com.hermes.hermetic.negocio.ultil.Util;
import pe.com.hermes.hermetic.web.controller.base.IController;
import pe.com.hermes.hermetic.web.controller.base.IWebOpciones;
import pe.com.hermes.hermetic.web.controller.general.MostrarReporteController;
import pe.com.hermes.hermetic.web.forms.HMF3014Form;

import pe.com.hermes.unidadesnegocio.comercial.entities.AtmEntity;
import pe.com.hermes.unidadesnegocio.comercial.entities.ClienteEntity;
import pe.com.hermes.unidadesnegocio.general.entities.TipoEntity;
import pe.com.hermes.unidadesnegocio.procesamiento.managerimpl.PedidoAbstract;



@Controller
@SessionAttributes(value={"codOpci","desOpci","listaPedidosAtm"})
@RequestMapping("/mostrarHWF3014.html")
public class ConsultaPedidoAtmController  implements IController{
  protected final Logger logger = Logger.getLogger(this.getClass());
  protected final static String TODOS = "0";
  protected final static String ALGUNOS = "1";  
  
  @Autowired
  private HermeticFacade servicioHermetic;
  @Autowired
  private MostrarReporteController reporteFactory;
  @Autowired
  private PedidoService pedidoService;
  @Autowired
  private TablService tablService;
  
  @RequestMapping(method=RequestMethod.GET)    
  protected String showForm(ModelMap model,HttpServletRequest request) throws Exception{
     HttpSession session = request.getSession(false); 
     HMF3014Form form = new HMF3014Form();
     form.setFormulario("HMR3014");
     String codSucuHtb = (String)request.getSession().getAttribute("sucursal");
     String cliente = (String)session.getAttribute("cliente");
     model.put("listaPedidosAtm","");
     session.setAttribute("chksSucu",null);
     session.setAttribute("chksPunto",null);
     session.setAttribute("chksTipPedi",null);
     session.setAttribute("prediccion",false);
     //List listaTipos = servicioHermetic.getTipoPedido();
     session.setAttribute("esSucuPrincipal",false);
     if (ConstantesHermetic.COD_SUCU_HTB_LIMA.equals(codSucuHtb)){
         model.put("esSucuPrincipal", true);
         session.setAttribute("esSucuPrincipal", true);
     }
     List listEstados = servicioHermetic.getListEstados();
     String fecha = servicioHermetic.getFechaHoy();
     form.setFechaDesde(fecha);
     form.setFechaHasta(fecha);
     form.setListEstados(listEstados);
     AuditBean auditBean = new AuditBean(PEDI_ATM);
     servicioHermetic.inseAudit(auditBean);
     String codOpci = IWebOpciones.PEDI_ATM;
     String desOpci = servicioHermetic.getDesOpci(codOpci, request);
     //model.put("listaTipos",listaTipos);
     //model.put("listSucursales",listSucursales);
     model.put("codOpci",codOpci);
     model.put("desOpci",desOpci);
     model.put(FORM_KEY,form);
     return  FORM_CONS_PEDI_ATM_VIEW;
  }
  
  @RequestMapping(params="accion=mostrar")
  private String mostrar (ModelMap model,@ModelAttribute(FORM_KEY) HMF3014Form form, BindingResult result, HttpServletRequest request) throws Exception {    
  
   HttpSession session = request.getSession(false);        
   if (request.getSession().getAttribute("usuario") == null)
       return FORM_SESSION_FINISH;

   List listaTransacciones = (List)session.getAttribute("listaMenu2");
   if (!Util.validaAccesoOpcion(listaTransacciones, ConstantesHermetic.CONSUL_PEDI_ATM)) {
       return FORM_ACCESS_NULL_VIEW;
   }    
   form.setControl(ConstantesHermetic.CTE_CONTROL_ACTIVO);
   
   //int accionMapa = 3;
   String cliente = (String)request.getSession().getAttribute("cliente");
   String[] chksPunto = (String[])session.getAttribute("chksPunto");
   String[] chksSucu = (String[])session.getAttribute("chksSucu"); 
   String[] chksTipPedi = (String[])session.getAttribute("chksTipPedi");
    
    List listEstados = servicioHermetic.getListEstados();
    form.setListEstados(listEstados);
   
   if(ALGUNOS.equals(form.getPunto()))
        if(Util.contDatosSession(chksPunto)<1){
            model.put("message_punto","Seleccione al menos un Tipo de Pedido");
            model.put("listaPedidosAtm","");
            return FORM_CONS_PEDI_ATM_VIEW;
        }
  if(ALGUNOS.equals(form.getSucursal()))
         if(Util.contDatosSession(chksSucu)<1){
            model.put("message_sucursal","Seleccione al menos un Tipo de Pedido");
            model.put("listaPedidosAtm","");
            return FORM_CONS_PEDI_ATM_VIEW;
         }
   if(ALGUNOS.equals(form.getTipPedido()))
       if(Util.contDatosSession(chksTipPedi)<1){
           model.put("message_tipoPedido","Seleccione al menos un Tipo de Pedido");
           model.put("listaPedidosAtm","");
           return FORM_CONS_PEDI_ATM_VIEW;
       }
    
   try {
       
       String codPuntos = null; 
       String codSucursales = null; 
       String codTipPedidos = null;
       
       if(TODOS.equals(form.getTipPedido())){ 
         chksTipPedi = null;
         session.setAttribute("chksTipPedi",chksTipPedi);
       }
       if(TODOS.equals(form.getPunto())){ 
         chksPunto = null;
         session.setAttribute("chksPunto",chksPunto);
       }
       if(TODOS.equals(form.getSucursal())){ 
         chksSucu = null;
         session.setAttribute("chksSucu",chksSucu); 
       }
       
       if(chksPunto!=null && chksPunto.length > 0) codPuntos = Util.arrayToString(chksPunto,","); else codPuntos = "0";
       if(chksSucu!=null && chksSucu.length > 0) codSucursales = Util.arrayToString(chksSucu,","); else codSucursales = "0";
       if(chksTipPedi!=null && chksTipPedi.length > 0) codTipPedidos = Util.arrayToString(chksTipPedi,","); else codTipPedidos = "0";
       
       if (session.getAttribute("esSucuPrincipal").equals(true)){
           model.put("esSucuPrincipal", true);
       }else{
          String codSucuHtb = (String)request.getSession().getAttribute("sucursal");
           codSucursales = codSucuHtb;
       }
       
       session.setAttribute("f_cliente",cliente);
       session.setAttribute("f_codSucursales", codSucursales);
       session.setAttribute("f_tipFecha", String.valueOf(form.getTipFecha()));
       session.setAttribute("f_fechaDesde", form.getFechaDesde());
       session.setAttribute("f_fechaHasta", form.getFechaHasta());
       session.setAttribute("f_codTipPedidos", codTipPedidos);
       
       
       int nroPedi = 0;
       if (request.getParameter("nroPedi").equalsIgnoreCase("")) {nroPedi = 0;}
       else{nroPedi = Integer.parseInt((String)request.getParameter("nroPedi"));};
       
       List<PedidoAbstract> listaPedidosAtm = new ArrayList();
       List<PedidoAbstract> listaPedidosAtmRecp = new ArrayList();
       List<PedidoAbstract> listaPedidosAtmPend = new ArrayList();
       PedidoAtmContainerManagerImpl pedidoContainer = new PedidoAtmContainerManagerImpl();
       
       int estado = form.getEstado();
       String estados;
       int indRecp=0;
       if (estado == ConstantesHermetic.STD_AUTZ){ indRecp = 0;};
       if (estado == ConstantesHermetic.STD_RECP_HERM){ indRecp = 1;};
       
       if (nroPedi == 0){
           if (estado == ConstantesHermetic.STD_AUTZ || estado == ConstantesHermetic.STD_RECP_HERM){// solo est_doc = 2                                                
                estados = String.valueOf(ConstantesHermetic.STD_AUTZ);
           listaPedidosAtm = servicioHermetic.getPedidosAtm(Integer.parseInt(cliente), codSucursales, form.getTipFecha(),form.getFechaDesde(),
                                                            form.getFechaHasta(), codPuntos, codTipPedidos, nroPedi, estados,0,ConstantesHermetic.TIP_PEDI_ATM, indRecp);
           
               if (indRecp==1){
                   for (PedidoAbstract pedidoAbstract:listaPedidosAtm){
                       pedidoAbstract.setEstDocu(5);
                   } 
               }
                
           }
           
           if (estado == 1){ //solo est_doc = 1
                estados = String.valueOf(estado);
                listaPedidosAtm = servicioHermetic.getPedidosAtmTemp(Integer.parseInt(cliente), codSucursales, form.getTipFecha(),form.getFechaDesde(),
                                                            form.getFechaHasta(), codPuntos, codTipPedidos, nroPedi, estados,0,ConstantesHermetic.TIP_PEDI_ATM);
           }
           
           if (estado == 0){ //solo est_doc in 1,2
               estados = new StringBuffer().append(ConstantesHermetic.STD_PEND).append(",").append(ConstantesHermetic.STD_AUTZ).toString();
               listaPedidosAtm = servicioHermetic.getPedidosAtm(Integer.parseInt(cliente), codSucursales, form.getTipFecha(),form.getFechaDesde(),
                                                            form.getFechaHasta(), codPuntos, codTipPedidos, nroPedi, estados,0,ConstantesHermetic.TIP_PEDI_ATM,0);
               listaPedidosAtmRecp = servicioHermetic.getPedidosAtm(Integer.parseInt(cliente), codSucursales, form.getTipFecha(),form.getFechaDesde(),
                                                          form.getFechaHasta(), codPuntos, codTipPedidos, nroPedi, estados,0,ConstantesHermetic.TIP_PEDI_ATM,1);
               
               for (PedidoAbstract pedidoAbstract:listaPedidosAtmRecp){
                   pedidoAbstract.setEstDocu(5);
               }
               
               listaPedidosAtm.addAll(listaPedidosAtmRecp);
               listaPedidosAtmPend = servicioHermetic.getPedidosAtmTemp(Integer.parseInt(cliente), codSucursales, form.getTipFecha(),form.getFechaDesde(),
                                                            form.getFechaHasta(), codPuntos, codTipPedidos, nroPedi, estados,0,ConstantesHermetic.TIP_PEDI_ATM);
               listaPedidosAtm.addAll(listaPedidosAtmPend);
           }
       }else{
           estados = new StringBuffer().append(ConstantesHermetic.STD_PEND).append(",").append(ConstantesHermetic.STD_AUTZ).toString();
           listaPedidosAtm = servicioHermetic.getPedidosAtmByNumero(ConstantesHermetic.TIP_PEDI_ATM, nroPedi, estados);
       }
       
       pedidoContainer.setPedidos(listaPedidosAtm);
       pedidoContainer.obtiListDenos();
       pedidoContainer.obtiListUnidMone();
       if ((request.getSession(false).getAttribute("prediccion")).equals(true)){ 
           form.setIsPrediction(true);
       }else{
           form.setIsPrediction(false);
       } //
       
       //session.setAttribute("prediccion",false);
       model.put("listDenos",pedidoContainer.obtiListDenos());
       model.put("listUnidMone",pedidoContainer.obtiListUnidMone());
       model.put("listaPedidosAtm",listaPedidosAtm);
     Map<Integer,String> mapEstados = new HashMap<Integer,String>();
     for (int i = 0; i < listEstados.size();i++){
       mapEstados.put(new Integer(((TiposBean)listEstados.get(i)).getCodigo()), ((TiposBean)listEstados.get(i)).getDescripcion());
     }
     model.put("mapEstados",mapEstados);
     form.setMapEstados(mapEstados);
       List listTipoPedi = servicioHermetic.buscarTipoIngresoPedido("");
       Map<Integer,String> mapTipos = new HashMap<Integer,String>();
       for (int i = 0; i < listTipoPedi.size();i++){
         mapTipos.put(new Integer(((TiposBean)listTipoPedi.get(i)).getCodigo()), ((TiposBean)listTipoPedi.get(i)).getDescripcion());
       }
       model.put("mapTipos",mapTipos);
       form.setMapTipos(mapTipos);
       model.put(FORM_KEY,form);         
   } catch (Exception e) {
       e.printStackTrace();
       //accionMapa = 0;
       return FORM_ERROR_VIEW;
   }

   return FORM_CONS_PEDI_ATM_VIEW;
  }
  
  @RequestMapping(params={"accion=openDetallePedido","numPedi","codSeri","tipDocuPedi"})
   protected String openDetallePedido(ModelMap model, @ModelAttribute("listaPedidosAtm") ArrayList<PedidoAbstract> listaPedidosAtm,
                                      HttpServletRequest request, @RequestParam("numPedi") String numPedi, @RequestParam("codSeri") String codSeri, 
                                                                                    @RequestParam("tipDocuPedi") String tipDocuPedi)throws Exception{
      HttpSession session = request.getSession(false);
      PedidoAtmManagerImpl pedidoSelected  = new PedidoAtmManagerImpl();
      List<ConfBean> listEstPedido = new ArrayList();
      String codClie = (String)session.getAttribute("cliente");
       
       try { 
             
             pedidoSelected.setCodSeriPedi(codSeri);
             pedidoSelected.setNumPedi(Integer.parseInt(numPedi));
             pedidoSelected.setTipDocuPedi(tipDocuPedi);
             int pedidoPosition = listaPedidosAtm.indexOf(pedidoSelected);
             pedidoSelected = (PedidoAtmManagerImpl)listaPedidosAtm.get(pedidoPosition);
             //****
           listEstPedido = (List<ConfBean>)tablService.getListLogConfNiv(codClie, tipDocuPedi, numPedi, codSeri);
         } catch (Exception nfe) {
             // TODO: Add catch code
             nfe.printStackTrace();
         }
       //listaPedidoDeno = (List<PedidoDenoEntity>)pedidoSelected.getDenosDetaPedido();
       model.put("pedidoSelected",pedidoSelected);
       model.put("listEstPedido",listEstPedido);
       model.put("listUnidMone",pedidoSelected.obtiListUnidMone());
       return FORM_CONS_DETA_PEDI_ATM_VIEW;
   }
  
  @RequestMapping(params="accion=verPDF")
  protected void verPDF(HttpSession session,HttpServletRequest request,HttpServletResponse response,
                        @ModelAttribute("listaPedidosAtm") ArrayList<PedidoAbstract> listaPedidosAtm,
                        @ModelAttribute(FORM_KEY) HMF3014Form form)throws Exception{
      try{
          String rutaJasper = session.getServletContext().getInitParameter("rutajasper");
          StringBuffer jasperPath = new StringBuffer(rutaJasper).append("/").append("HMR3014").append(".jasper");
          Map map = new HashMap();
          Map subReportDS1 = new HashMap();
          JRDataSource simpleDS;
          String fecha_srv = servicioHermetic.getFechaHoy();
          String hora_srv = servicioHermetic.getFecha2().substring(8, 13);
          String fecSoliPedi = null;
          String horSoliPedi = null;
          
          PedidoAtmContainerManagerImpl _pedidoContainer = new PedidoAtmContainerManagerImpl();
          _pedidoContainer.setPedidos(listaPedidosAtm);
          simpleDS = new JRBeanCollectionDataSource(_pedidoContainer.getPedidos());
          map.put("nomClie",(String)session.getAttribute("nombreCliente"));
          map.put("fec_soli_pedi_desd",form.getFechaDesde());
          map.put("fec_soli_pedi_hast",form.getFechaHasta());
          map.put("fec_soli_pedi", _pedidoContainer.getFecSoliPedi());
          map.put("hor_soli_pedi",_pedidoContainer.getHorSoliPedi());
          map.put("usuWeb",Util.getUser().getUsuWeb());
          map.put("nomUsua",Util.getUser().getPriNomb()+" "+Util.getUser().getPriApel());
          map.put("fecha_srv",fecha_srv);
          map.put("hora_srv",hora_srv);
          map.put("subReportDS1",subReportDS1);
          map.put("contextPath",request.getSession().getServletContext().getRealPath("/"));
          ServletOutputStream servletOutputStream = response.getOutputStream();
          InputStream reportStream = session.getServletContext().getResourceAsStream(jasperPath.toString());
          byte[] bytes = null;        
          bytes = JasperRunManager.runReportToPdf(reportStream, map, simpleDS);
          response.setHeader("Cache-Control","cache"); // HTTP 1.1
          response.setHeader("Pragma","cache"); // HTTP 1.0
          response.setDateHeader ("Expires", -1);         
          response.setContentType("application/pdf");
          response.addHeader("Content-Disposition", "inline; filename=Reporte.pdf");        
          response.setContentLength(bytes.length);         
          servletOutputStream.write(bytes, 0, bytes.length);
          servletOutputStream.flush();
          servletOutputStream.close();
      }catch(Exception e){
          logger.error(e);
          e.printStackTrace();
      }    
  }
  
  @RequestMapping(params="accion=mostrarExcel")
  protected void mostrarExcel(ModelMap model,HttpSession session,HttpServletRequest request,HttpServletResponse response,
                              @ModelAttribute("listaPedidosAtm") ArrayList<PedidoAbstract> listaPedidosAtm,
                              @ModelAttribute(FORM_KEY) HMF3014Form form)throws Exception{        
      try{
          
          PedidoAtmContainerManagerImpl pedidosContainer = new PedidoAtmContainerManagerImpl();
          ClienteEntity clieOrig = new ClienteEntity(Integer.parseInt((String)session.getAttribute("cliente")),(String)session.getAttribute("nombreCliente"));
          pedidosContainer.setClieOrig(clieOrig);
          pedidosContainer.setPedidos(listaPedidosAtm);
          HSSFWorkbook wb = new HSSFWorkbook(); 
          wb=pedidoService.excelMostrarPedidosAtm(pedidosContainer, form);
          response.addHeader("Content-type", "application/vnd.ms-excel");
          response.addHeader("Content-Disposition", "attachment; filename=ConsultaPedidosATM.xls");
          response.setContentType("Content-type: application/vnd.ms-excel");
          
          response.setHeader("Cache-Control","cache"); // HTTP 1.1
          response.setHeader("Pragma","cache"); // HTTP 1.0
          response.setDateHeader ("Expires", -1);  
          
          OutputStream out = response.getOutputStream();
          wb.write(out);
          out.close();
      }catch(Exception e){
          logger.error(e);
          e.printStackTrace();
      }    
  }
  
  @RequestMapping(params="accion=mostrarExcelPred")
  protected void mostrarExcelPred(ModelMap model,HttpSession session,HttpServletRequest request,HttpServletResponse response,
                                  @ModelAttribute("listaPedidosAtm") ArrayList<PedidoAbstract> listaPedidosAtm,
                                  @ModelAttribute(FORM_KEY) HMF3014Form form) throws Exception{        
      try{
          PedidoAtmContainerManagerImpl pedidosContainer = new PedidoAtmContainerManagerImpl();
          //ClienteEntity clieOrig = new ClienteEntity(Integer.parseInt((String)session.getAttribute("cliente")),(String)session.getAttribute("nombreCliente"));
          
          String cliente = (String)session.getAttribute("f_cliente");
          String codSucursales = (String)session.getAttribute("f_codSucursales");
          String tipFecha = (String)session.getAttribute("f_tipFecha");
          String fechaDesde = (String)session.getAttribute("f_fechaDesde");
          String fechaHasta = (String)session.getAttribute("f_fechaHasta");
          String codTipPedidos = (String)session.getAttribute("f_codTipPedidos");
          String chk_repo = "0"; // 1-INTK_LIMA // 2-CONTI // 3-GENERAL
          List<PedidoAbstract> listaPedidosAtmToPred = servicioHermetic.getPedidosAtmToPred(Integer.parseInt(cliente), codTipPedidos,tipFecha, fechaDesde, fechaHasta, codSucursales);;
          
          
          if (session.getAttribute("cliente").equals(ConstantesHermetic.COD_CLIENTE_INTERBANK)){ 
            chk_repo = "1"; //INTERBANK-LIMA
          }else{          
              if (session.getAttribute("cliente").equals(ConstantesHermetic.COD_CLIENTE_CONTINENTAL)){
                Collections.sort(listaPedidosAtmToPred,PedidoAtmManagerImpl.ORDER_BY_CONF_DISP);
                chk_repo = "2"; //CONTINENTAL
              }else{ 
                chk_repo = "3";  // GENERAL
                form.setDesRazoSoci((String)session.getAttribute("nombreCliente"));
              }
          }
          
          pedidosContainer.setPedidos(listaPedidosAtmToPred);    
          HSSFWorkbook wb = new HSSFWorkbook(); 
          wb=pedidoService.excelMostrarPedidosPredAtm(pedidosContainer, form, chk_repo);              
          response.addHeader("Content-type", "application/vnd.ms-excel");
          response.addHeader("Content-Disposition", "attachment; filename=ReportesPrediccionATM.xls");
          response.setContentType("Content-type: application/vnd.ms-excel");
          
          response.setHeader("Cache-Control","cache"); // HTTP 1.1
          response.setHeader("Pragma","cache"); // HTTP 1.0
          response.setDateHeader ("Expires", -1);  
          
          OutputStream out = response.getOutputStream();
          wb.write(out);
          out.close();
      }catch(Exception e){
          logger.error(e);
          e.printStackTrace();
      }    
  }
}
